// package com.allen.study.common.utils;
//
// import com.allen.study.common.exception.CamundaProcessException;
// import lombok.extern.slf4j.Slf4j;
// import org.camunda.bpm.engine.*;
// import org.camunda.bpm.engine.history.HistoricActivityInstance;
// import org.camunda.bpm.engine.history.HistoricActivityInstanceQuery;
// import org.camunda.bpm.engine.history.HistoricProcessInstance;
// import org.camunda.bpm.engine.history.HistoricTaskInstance;
// import org.camunda.bpm.engine.repository.Deployment;
// import org.camunda.bpm.engine.repository.DeploymentBuilder;
// import org.camunda.bpm.engine.repository.ProcessDefinition;
// import org.camunda.bpm.engine.runtime.ActivityInstance;
// import org.camunda.bpm.engine.runtime.ProcessInstance;
// import org.camunda.bpm.engine.task.Task;
// import org.camunda.bpm.model.bpmn.BpmnModelInstance;
// import org.camunda.bpm.model.bpmn.instance.FlowNode;
// import org.camunda.bpm.model.bpmn.instance.SequenceFlow;
// import org.camunda.bpm.model.bpmn.instance.UserTask;
// import org.camunda.bpm.model.xml.instance.ModelElementInstance;
//
// import java.util.Collection;
// import java.util.List;
// import java.util.Map;
// import java.util.stream.Collectors;
//
// /**
//  * @ClassName: CamundaUtils
//  * @Author: AllenSun
//  * @Date: 2025/2/20 下午11:42
//  */
// // Camunda 工具类，封装了所有用到的 Camunda 方法
// // http://localhost:8081/camunda/
// @Slf4j
// public class CamundaUtils {
//     private static final ProcessEngine processEngine = ProcessEngines.getDefaultProcessEngine();
//     private static final RuntimeService runtimeService = processEngine.getRuntimeService();
//     private static final TaskService taskService = processEngine.getTaskService();
//     private static final RepositoryService repositoryService = processEngine.getRepositoryService();
//     private static final HistoryService historyService = processEngine.getHistoryService();
//
//     /**
//      * 通过类路径部署流程
//      * @param deploymentName 部署名称
//      * @param classpathResource 类路径下的资源名称
//      * @return 部署对象
//      */
//     public static Deployment deployProcessByClasspath(String deploymentName, String classpathResource) {
//         Deployment deploy = null;
//         try {
//             DeploymentBuilder deploymentBuilder = repositoryService.createDeployment()
//                     .name(deploymentName)
//                     .addClasspathResource(classpathResource);
//             deploy = deploymentBuilder.deploy();
//         } catch (Exception e) {
//             log.error("流程部署失败:{}",e.getMessage());
//             throw new CamundaProcessException("流程部署失败");
//         }
//         log.info("流程部署成功:{}",deploy.getId());
//
//         return deploy;
//     }
//
//
//     /**
//      * 根据部署key查询部署的流程
//      * @MethodName: listProcessInstanceByKey
//      * @Author: AllenSun
//      * @Date: 2025/2/22 下午11:56
//      */
//     public static ProcessDefinition selectProcessDefinitionByKey(String processDefinitionKey) {
//         // 根据流程定义键和业务键查询流程实例
//         ProcessDefinition processDefinition = null;
//         try {
//             processDefinition = repositoryService.createProcessDefinitionQuery()
//                     .processDefinitionKey(processDefinitionKey)
//                     .latestVersion()
//                     .singleResult();
//         } catch (Exception e) {
//             log.error("查询部署流程信息失败：{}",e.getMessage());
//             throw new CamundaProcessException("查询失败");
//         }
//         return processDefinition;
//     }
//
//     /**
//      * 判断流程是否已部署
//      * @MethodName: isProcessDefinitionExists
//      * @Author: AllenSun
//      * @Date: 2025/2/22 下午11:59
//      */
//     public static boolean isProcessDefinitionExists(String processDefinitionKey) {
//         return selectProcessDefinitionByKey(processDefinitionKey) != null;
//     }
//
//
//     /**
//      * 启动流程实例
//      * @param processDefinitionKey 流程定义的 Key，对应 BPMN 文件中的流程定义 ID
//      * @param variables 流程变量，用于传递业务数据
//      * @return 流程实例 ID
//      */
//     public static String startProcessInstance(String processDefinitionKey, Map<String, Object> variables) {
//         if(!isProcessDefinitionExists(processDefinitionKey)){
//             throw new CamundaProcessException("流程未部署");
//         }
//         ProcessInstance processInstance = null;
//         try {
//             processInstance = runtimeService.startProcessInstanceByKey(processDefinitionKey, variables);
//         } catch (Exception e) {
//             log.error("流程启动失败:{}:{}",processDefinitionKey,e.getMessage());
//             throw new CamundaProcessException("流程启动失败");
//         }
//         log.info("流程启动成功：{}",processDefinitionKey);
//         return processInstance.getId();
//     }
//
//     /**
//      * 判断指定流程定义键和业务键的流程实例是否已经创建
//      * @param processDefinitionKey 流程定义键
//      * @return 如果流程实例已存在返回 true，否则返回 false
//      */
//     public static boolean isProcessInstanceExists(String processDefinitionKey) {
//         // 根据流程定义键和业务键查询流程实例
//         List<ProcessInstance> processInstances = runtimeService.createProcessInstanceQuery()
//                 .processDefinitionKey(processDefinitionKey)
//                 .list();
//         return !processInstances.isEmpty();
//     }
//
//     /**
//      * 完成任务
//      * @param taskId 任务 ID
//      * @param variables 任务变量，用于传递审批结果和理由等信息
//      */
//     public static void completeTask(String taskId, Map<String, Object> variables) {
//         taskService.complete(taskId, variables);
//     }
//
//     /**
//      * 获取指定用户的待办任务列表
//      * @param assignee 任务负责人的工号
//      * @param pageNum 页码
//      * @param pageSize 每页数量
//      * @return 待办任务列表
//      */
//     public static List<Task> getTasksByAssignee(String assignee, int pageNum, int pageSize) {
//         List<Task> tasks = taskService.createTaskQuery()
//                 .taskAssignee(assignee)
//                 .listPage((pageNum - 1) * pageSize, pageSize);
//         return tasks;
//     }
//
//     /**
//      * 获取指定用户的已办任务列表
//      * @param assignee 任务负责人的工号
//      * @param pageNum 页码
//      * @param pageSize 每页数量
//      * @return 已办任务列表
//      */
//     public static List<HistoricTaskInstance> getCompletedTasksByAssignee(String assignee, int pageNum, int pageSize) {
//         return historyService
//                 .createHistoricTaskInstanceQuery()
//                 .taskAssignee(assignee)
//                 .finished()
//                 .listPage((pageNum - 1) * pageSize, pageSize);
//     }
//
//     /**
//      * 获取指定流程实例的历史活动实例列表
//      * @param processInstanceId 流程实例 ID
//      * @return 历史活动实例列表
//      */
//     public static List<HistoricActivityInstance> getHistoricActivityInstances(String processInstanceId) {
//         HistoricActivityInstanceQuery query = historyService
//                 .createHistoricActivityInstanceQuery()
//                 .processInstanceId(processInstanceId);
//         return query.list();
//     }
//
//     /**
//      * 获取指定流程实例的历史流程实例
//      * @param processInstanceId 流程实例 ID
//      * @return 历史流程实例
//      */
//     public static HistoricProcessInstance getHistoricProcessInstance(String processInstanceId) {
//         return historyService
//                 .createHistoricProcessInstanceQuery()
//                 .processInstanceId(processInstanceId)
//                 .singleResult();
//     }
//
//     /**
//      * 终止流程实例
//      * @param processInstanceId 流程实例 ID
//      * @param deleteReason 终止原因
//      */
//     public static void terminateProcessInstance(String processInstanceId, String deleteReason) {
//         runtimeService.deleteProcessInstance(processInstanceId, deleteReason);
//     }
//
//     /**
//      * 获取指定流程实例的当前任务
//      * @param processInstanceId 流程实例 ID
//      * @return 当前任务
//      */
//     public static Task getCurrentTask(String processInstanceId) {
//         return taskService.createTaskQuery()
//                 .processInstanceId(processInstanceId)
//                 .singleResult();
//     }
//
//     /**
//      * 转交任务
//      * @MethodName: transferTask
//      * @Author: AllenSun
//      * @Date: 2025/2/23 下午3:37
//      */
//     public static Boolean transferTask(String taskId, String assigneeId){
//         try {
//             taskService.setAssignee(taskId, assigneeId);
//         } catch (Exception e) {
//             log.error("任务转交失败：{}",e.getMessage());
//             throw new CamundaProcessException("任务转交失败");
//         }
//         return true;
//     }
//
//
//     /**
//      * 驳回处理
//      * @MethodName: rejectTask
//      * @Author: AllenSun
//      * @Date: 2025/2/23 下午9:06
//      */
//     public static Boolean rejectTask(String processInstanceId, String targetNodeId){
//         try {
//             //获取当前环节实例 这是个树结构
//             ActivityInstance activity = runtimeService.getActivityInstance(processInstanceId);
//
//             //获取实例的流程定义 这里主要是为了拿到节点前的那条线的Id
//             List<HistoricActivityInstance> hisActivityList = historyService.createHistoricActivityInstanceQuery().processInstanceId(processInstanceId).finished().list();
//             List<String> nodeIds = hisActivityList.stream().map(HistoricActivityInstance::getActivityId).collect(Collectors.toList());
//
//             ProcessInstance processInstance = runtimeService.createProcessInstanceQuery().processInstanceId(processInstanceId).singleResult();
//             BpmnModelInstance bpmnModel = repositoryService.getBpmnModelInstance(processInstance.getProcessDefinitionId());
//             ModelElementInstance modelElement = bpmnModel.getModelElementById(targetNodeId);
//             UserTask userTask = (UserTask) modelElement;
//             Collection<SequenceFlow> incoming = userTask.getIncoming();
//             String transitionId = "";
//             for (SequenceFlow sequenceFlow : incoming) {
//                 FlowNode source = sequenceFlow.getSource();
//                 if (nodeIds.contains(source.getId())) {
//                     transitionId = sequenceFlow.getId();
//                     break;
//                 }
//             }
//
//             runtimeService.createProcessInstanceModification(processInstanceId)
//                     //取消现有的活动实例
//                     .cancelActivityInstance(activity.getId())
//                     //设置备注
//                     .setAnnotation("驳回")
//                     .startTransition(transitionId)
//                     .execute();
//         } catch (Exception e) {
//             log.error("驳回处理失败：{}",e.getMessage());
//             throw new CamundaProcessException("驳回处理失败");
//         }
//         return true;
//     }
//
//
// }
